package org.bspv.pharma.manager.impl;

import java.util.List;

import javax.persistence.EntityExistsException;

import org.bspv.pharma.common.exception.UserExistsException;
import org.bspv.pharma.dao.UserDAO;
import org.bspv.pharma.manager.UserManager;
import org.bspv.pharma.model.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

/**
 * 
 * @author guillaume
 * 
 */
@Service(value = "userManager")
public class UserManagerImpl extends AbstractManagerImpl<User, Long> implements
		UserManager {

	@Autowired
	public UserManagerImpl(UserDAO dao) {
		super(dao);
	}

	/**
	 * {@inheritDoc}
	 */
	public User getUser(String userId) {
		return dao.findById(new Long(userId));
	}

	/**
	 * {@inheritDoc}
	 */
	public List<User> getUsers(User user) {
		return dao.findAll();
	}

	/**
	 * {@inheritDoc}
	 */
	public Long saveUser(User user) throws UserExistsException {

		try {
			return dao.save(user);
		} catch (DataIntegrityViolationException e) {
			e.printStackTrace();
			log.warn(e.getMessage());
			throw new UserExistsException("User '" + user.getUsername()
					+ "' already exists!");
		} catch (EntityExistsException e) { // needed for JPA
			e.printStackTrace();
			log.warn(e.getMessage());
			throw new UserExistsException("User '" + user.getUsername()
					+ "' already exists!");
		}
	}

	/**
	 * {@inheritDoc}
	 */
	public void removeUser(String username) {
		User u = dao.findUniqueResultBy("username", username);
		log.debug("removing user: " + username);
		dao.delete(u);
	}

	/**
	 * {@inheritDoc}
	 * 
	 * @param username
	 *            the login name of the human
	 * @return User the populated user object
	 * @throws UsernameNotFoundException
	 *             thrown when username not found
	 */
	public User getUserByUsername(String username)
			throws UsernameNotFoundException {
		return (User) dao.findUniqueResultBy("username", username);
	}
}
